﻿using LCL.Network.Profinet.Panasonic;
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.IO.Ports;
using System.Linq;
using System.Text;
using System.Threading;
using System.Windows.Forms;

namespace LCL.NetworkDemo.PLC
{
    public partial class FormPanasonicMew : Form
    {
        private PanasonicMewtocol panasonicMewtocol = null;
        public FormPanasonicMew()
        {
            InitializeComponent();
        }

        private void FormPanasonicMew_Load(object sender, EventArgs e)
        {
            panel2.Enabled = false;
            userCurve1.SetLeftCurve("A", new float[0], Color.Tomato);
            comboBox1.SelectedIndex = 0;
            comboBox2.DataSource = SerialPort.GetPortNames();
            try
            {
                comboBox2.SelectedIndex = 0;
            }
            catch
            {
                comboBox2.Text = "COM3";
            }
            if (!Program.ShowAuthorInfomation)
            {
                label2.Visible = false;
                linkLabel1.Visible = false;
                label20.Visible = false;
            }
        }
        #region 连接/断开连接
        private void butConnect_Click(object sender, EventArgs e)
        {
            int baudRate,dataBits,stopBits;
            byte station;
            if(!int.TryParse(textBox2.Text,out baudRate ))
            {
                MessageBox.Show( "波特率输入错误！" );
                return;
            }
            if (!int.TryParse( textBox16.Text, out dataBits ))
            {
                MessageBox.Show( "数据位输入错误！" );
                return;
            }
            if (!int.TryParse( textBox17.Text, out stopBits ))
            {
                MessageBox.Show( "停止位输入错误！" );
                return;
            }
            if (!byte.TryParse(textBox15.Text,out station))
            {
                MessageBox.Show( "站号输入不正确！" );
                return;
            }
            panasonicMewtocol.Close( );
            panasonicMewtocol = new PanasonicMewtocol( station );
            try
            {
                panasonicMewtocol.SerialPortInni( sp =>
                 {
                     sp.PortName = comboBox2.Text;
                     sp.BaudRate = baudRate;
                     sp.DataBits = dataBits;
                     sp.StopBits = stopBits == 0 ? System.IO.Ports.StopBits.None : (stopBits == 1 ? System.IO.Ports.StopBits.One : System.IO.Ports.StopBits.Two);
                     sp.Parity = comboBox1.SelectedIndex == 0 ? System.IO.Ports.Parity.None : (comboBox1.SelectedIndex == 1 ? System.IO.Ports.Parity.Odd : System.IO.Ports.Parity.Even);
                 } );
                panasonicMewtocol.Open( );

                button2.Enabled = true;
                button1.Enabled = false;
                panel2.Enabled = true;
            }
            catch (Exception ex)
            {
                MessageBox.Show( ex.Message );
            }
        }
        private void butDisconnect_Click(object sender, EventArgs e)
        {
            // 断开连接
            panasonicMewtocol.Close();
            button2.Enabled = false;
            button1.Enabled = true;
            panel2.Enabled = false;
        }
        #endregion

        #region 统一读取写入数据
        /// <summary>
        /// 统一的读取结果的数据解析，显示
        /// </summary>
        private void readResultRender<T>(Result<T> result, string address, TextBox textBox)
        {
            if (result.Success)
            {
                textBox.AppendText(DateTime.Now.ToString("[HH:mm:ss] ")
                    + "[" + address + "] " + result.Data + "" + Environment.NewLine + "");
            }
            else
            {
                MessageBox.Show(DateTime.Now.ToString("[HH:mm:ss] ")
                    + "[" + address + "] 读取失败" + Environment.NewLine + "原因：" + result.ToMessageShowString() + "");
            }
        }
        /// <summary>
        /// 统一的数据写入的结果显示
        /// </summary>
        private void writeResultRender(Result result, string address)
        {
            if (result.Success)
            {
                MessageBox.Show(DateTime.Now.ToString("[HH:mm:ss] ") + "[" + address + "] 写入成功");
            }
            else
            {
                MessageBox.Show(DateTime.Now.ToString("[HH:mm:ss] ")
                    + "[" + address + "] 写入失败" + Environment.NewLine + "原因：" + result.ToMessageShowString() + "");
            }
        }
        #endregion

        //单数据读取测试
        private void butRead_Click(object sender, EventArgs e)
        { //单数据读取测试
            string memory = this.txtMemory.Text.ToUpper().Trim();
            string address = this.txtAddress.Text.Trim();
            string length = this.txtLength.Text.Trim();
            string dataType = this.txtDataType.Text.ToLower().Trim();

            string add = memory + address;
            switch (dataType)
            {
                case "bool":
                    // 读取bool变量
                    readResultRender(panasonicMewtocol.ReadBool(add), add, txtResult);
                    break;
                case "short":
                    readResultRender(panasonicMewtocol.ReadInt16(add), add, txtResult);
                    break;
                case "ushort":
                    readResultRender(panasonicMewtocol.ReadUInt16(add), add, txtResult);
                    break;
                case "int":
                    readResultRender(panasonicMewtocol.ReadInt32(add), add, txtResult);
                    break;
                case "uint":
                    readResultRender(panasonicMewtocol.ReadUInt32(add), add, txtResult);
                    break;
                case "long":
                    readResultRender(panasonicMewtocol.ReadInt64(add), add, txtResult);
                    break;
                case "ulong":
                    readResultRender(panasonicMewtocol.ReadUInt64(add), add, txtResult);
                    break;
                case "float":
                    readResultRender(panasonicMewtocol.ReadFloat(add), add, txtResult);
                    break;
                case "double":
                    readResultRender(panasonicMewtocol.ReadDouble(add), add, txtResult);
                    break;
                case "string":
                    readResultRender(panasonicMewtocol.ReadString(add, ushort.Parse(txtLength.Text)), add, txtResult);
                    break;
                default:
                    break;
            }
        }
        //单数据写入测试
        private void butWrite_Click(object sender, EventArgs e)
        {//单数据写入测试
            string memory = this.txtMemory.Text.ToUpper().Trim();
            string address = this.txtAddress.Text.Trim();
            string length = this.txtLength.Text.Trim();
            string dataType = this.txtDataType.Text.ToLower().Trim();
            string value = this.txtValue.Text.Trim();

            string add = memory + address;
            switch (dataType)
            {
                case "bool":
                    writeResultRender(panasonicMewtocol.Write(add, bool.Parse(value)), add);
                    break;
                case "byte":
                    writeResultRender(panasonicMewtocol.Write(add, byte.Parse(value)), add);
                    break;
                case "short":
                    writeResultRender(panasonicMewtocol.Write(add, short.Parse(value)), add);
                    break;
                case "ushort":
                    writeResultRender(panasonicMewtocol.Write(add, ushort.Parse(value)), add);
                    break;
                case "int":
                    writeResultRender(panasonicMewtocol.Write(add, int.Parse(value)), add);
                    break;
                case "uint":
                    writeResultRender(panasonicMewtocol.Write(add, uint.Parse(value)), add);
                    break;
                case "long":
                    writeResultRender(panasonicMewtocol.Write(add, long.Parse(value)), add);
                    break;
                case "ulong":
                    writeResultRender(panasonicMewtocol.Write(add, ulong.Parse(value)), add);
                    break;
                case "float":
                    writeResultRender(panasonicMewtocol.Write(add, float.Parse(value)), add);
                    break;
                case "double":
                    writeResultRender(panasonicMewtocol.Write(add, double.Parse(value)), add);
                    break;
                case "string":
                    writeResultRender(panasonicMewtocol.Write(add, value), add);
                    break;
                default:
                    break;
            }
        }
        //批量读取
        private void butBatchRead_Click(object sender, EventArgs e)
        {
            try
            {
                string memory = this.txtMemory.Text.ToUpper().Trim();
                string address = this.txtAddress.Text.Trim();
                string length = this.txtLength.Text.Trim();
                string dataType = this.txtDataType.Text.ToLower().Trim();

                string add = memory + address;
                Result<byte[]> read = panasonicMewtocol.Read(add, ushort.Parse(length));
                if (read.Success)
                {
                    // 此处需要根据实际的情况来自定义来处理复杂的数据
                    //short D100 = panasonicMewtocol.ByteTransform.TransInt16(read.Data, 0);
                    //short D101 = panasonicMewtocol.ByteTransform.TransInt16(read.Data, 2);
                    //short D102 = panasonicMewtocol.ByteTransform.TransInt16(read.Data, 4);
                    //short D103 = panasonicMewtocol.ByteTransform.TransInt16(read.Data, 6);
                    //short D104 = panasonicMewtocol.ByteTransform.TransInt16(read.Data, 7);

                    this.txtResult.Text = "结果：" + Utils.ByteToHexString(read.Data);
                }
                else
                {
                    MessageBox.Show("读取失败：" + read.ToMessageShowString());
                }
            }
            catch (Exception ex)
            {
                MessageBox.Show("读取失败：" + ex.Message);
            }
        }
        //报文读取
        private void butMessage_Click(object sender, EventArgs e)
        {
            try
            {
                Result<byte[]> read = panasonicMewtocol.ReadBase(Utils.HexStringToBytes(txtMessage.Text));
                if (read.Success)
                {
                    txtResult.Text = "结果：" + Utils.ByteToHexString(read.Data);
                }
                else
                {
                    MessageBox.Show("读取失败：" + read.ToMessageShowString());
                }
            }
            catch (Exception ex)
            {
                MessageBox.Show("读取失败：" + ex.Message);
            }
        }

        #region  定时器读取测试
        private Thread thread = null;// 后台读取的线程
        private int timeSleep = 300; // 读取的间隔
        private bool isThreadRun = false; // 用来标记线程的运行状态
        //定时器读取测试
        private void butCurve_Click(object sender, EventArgs e)
        {
            // 启动后台线程，定时读取PLC中的数据，然后在曲线控件中显示
            if (!isThreadRun)
            {
                if (!int.TryParse(textBox14.Text, out timeSleep))
                {
                    MessageBox.Show("间隔时间格式输入错误！");
                    return;
                }
                butCurve.Text = "停止";
                isThreadRun = true;
                thread = new Thread(ThreadReadServer);
                thread.IsBackground = true;
                thread.Start();
            }
            else
            {
                butCurve.Text = "启动";
                isThreadRun = false;
            }
        }
        private void ThreadReadServer()
        {
            string add = this.textBox12.Text;
            while (isThreadRun)
            {
                Thread.Sleep(timeSleep);
                try
                {
                    Result<short> read = panasonicMewtocol.ReadInt16(add);
                    if (read.Success)
                    {
                        // 显示曲线
                        if (isThreadRun) Invoke(new Action<short>(AddDataCurve), read.Data);
                    }
                }
                catch (Exception ex)
                {
                    MessageBox.Show("读取失败：" + ex.Message);
                }

            }
        }
        private void AddDataCurve(short data)
        {
            userCurve1.AddCurveData("A", data);
        }
        #endregion

        private void FormMelsecSerial_FormClosing(object sender, FormClosingEventArgs e)
        {
            isThreadRun = false;
        }

      
    }
}
